import serial
import serial.tools.list_ports
import time
import os
import sys
import re
import datetime
 
class serialObj(object):
 # 初始化串口对象，设置多个串口并连接
 def __init__(self,**ports):
  # self.at_port = ""	
  # self.at_serial = None
  # if "at_port" in ports:
  # 	self.at_port = ports["at_port"]
  
    
  if "at_port" in ports:
   try:
    self.at_serial = serial.Serial(ports["at_port"],115200)
   except:
    print("at口[{}]连接失败，请检查端口".format(ports["at_port"]))
    sys.exit()
 
  if "aux_at_port" in ports:
   try:
    self.aux_at_serial = serial.Serial(ports["aux_at_port"],115200)
   except:
    print("aux_at口[{}]连接失败，请检查端口".format(ports["aux_at_port"]))
    sys.exit()
 
  if "debug_port" in ports:
   try:
    self.debug_serial = serial.Serial(ports["debug_port"],115200)
   except:
    print("debug口[{}]连接失败，请检查端口".format(ports["debug_port"]))
    sys.exit()
     
  if "aux_debug_port" in ports:
   try:
    self.aux_debug_port = serial.Serial(ports["aux_debug_port"],115200)
   except:
    print("debug口[{}]连接失败，请检查端口".format(ports["aux_debug_port"]))
    sys.exit()
 
  if "modem_port" in ports:
   try:
    self.modem_serial = serial.Serial(ports["modem_port"],115200)
   except:
    print("modem口[{}]连接失败，请检查端口".format(ports["modem_port"]))
    sys.exit()
  if "uart_port" in ports:
   try:
    self.uart_serial = serial.Serial(ports["uart_port"],115200)
   except:
    print("uart口[{}]连接失败，请检查端口".format(ports["uart_port"]))
    sys.exit()
  if "relay_port" in ports:
   try:
    self.relay_serial = serial.Serial(ports["relay_port"],9600)
   except:
    print("继电器口[{}]连接失败，请检查端口".format(ports["relay_port"]))
    sys.exit()
 # 获取AT串口
 def get_at_serial(self):
  return self.at_serial
 
 # 获取调试串口
 def get_debug_serial(self):
  return self.debug_serial
 
 # 获取UART串口
 def get_uart_serial(self):
  return self.uart_serial
 
 # 获取调制解调器串口
 def get_modem_serial(self):
  return self.modem_serial
 
 # 获取继电器串口
 def get_relay_serial(self):
  return self.relay_serial
 
 # 关闭模块供电
 def powerOff(self):
  self.uart_serial.dtr = True
  print("power off ---Module power down\n")
 
 # 开启模块供电
 def powerOn(self):
  self.uart_serial.dtr = False
  print("power on ---Module power up\n")
 
 # 发送at指令
 def serial_write(self,serial_port ,command):
  send_command = command.encode("UTF-8")
  serial_port.write(send_command)
 
 # 读取at口返回
 def serial_read(self,serial_port,logFile=""):
  global rec_str_time
  rec_str = ''
  for i in range(3):
   time.sleep(0.1)
   lenth = serial_port.inWaiting()
   rec_str = serial_port.read(lenth)
   try:
    rec_str = re.sub('\\x1b.*?m', "", rec_str.decode("UTF-8"), 0, re.I)
    for i in rec_str.split('\n'):
     if i == '' or i == '\r' or i == '\n' or i == '\r\n':
      continue
     else:
      rec_str_time = '[{0}]   {1}\n'.format(
       time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()),
       (i + '\n').replace('\r', '').replace('\n', ''))
      if logFile != "":
       with open(logFile, 'a') as file_object:
        file_object.write(rec_str_time)
    return rec_str
   except:
    return ""
  return rec_str
 
 # 重新查找网络并记录
 def refindNetwork(self,logFile):
  self.serial_write(self.at_serial,"AT+CFUN=0\r\n")
  time.sleep(1)
  self.serial_write(self.at_serial,"AT+CFUN=1\r\n")
  result = self.serial_read(self.at_serial)
  result1 = '{} {}'.format(rec_str_time, result)
  with open(logFile, 'a') as file_object:
   file_object.write(result1)
 
  findNetworkCnt = 0
  #找网失败则返回0，十位表示网络制式，各位表示找网等级 1、good 2、normal 3、poor 4、bad
  currentNetwork = 0
  while True:
   findNetworkCnt += 1
   self.serial_write(self.at_serial,"AT+CREG?;+CGREG?;+CEREG?;+COPS?;+QCSQ;+QNWINFO\r\n")
   result = self.serial_read(self.at_serial)
   result1 = '{} {}'.format(rec_str_time, result)
   with open(logFile, 'a') as file_object:
    file_object.write(result1)
 
   # 这里判断是否找到4G
   if ("+CGREG: 0,1" in result) and ("+CEREG: 0,1" in result) and (("+CREG: 0,3" in result) or ("+CREG: 0,1" in result)) and ("LTE" in result):
    print("find 4G success\n")
    currentNetwork = 40
   # 这里判断是否找到5G
   elif ("+CGREG: 0,1" in result) and ("+CEREG: 0,1" in result) and (("+CREG: 0,0" in result) or ("+CREG: 0,1" in result)) and ("NR5G" in result):
    print("find 5G success\n")
    currentNetwork = 50
 
   if findNetworkCnt <= 60:
    if currentNetwork != 0:
     if findNetworkCnt > 40:
      print("find network success,singal bad\n")
      currentNetwork += 4
     elif findNetworkCnt > 20:
      print("find network success,singal poor\n")
      currentNetwork += 3
     elif findNetworkCnt > 10:
      print("find network success,singal normal\n")
      currentNetwork += 2
     else:
      print("find network success,singal good\n")
      currentNetwork += 1
     return currentNetwork
   else:
    print("find network failed\n")
    currentNetwork = 0
    return currentNetwork
    
 # 检查当前网络状态
 def checkCurrentNetwork(self,logFile,exceptNetwork):
  self.serial_write(self.at_serial,"AT+CREG?;+CGREG?;+CEREG?;+COPS?;+QCSQ;+QNWINFO\r\n")
  result = self.serial_read(self.at_serial)
  if "4G" == exceptNetwork:
   if ("+CGREG: 0,1" in result) and ("+CEREG: 0,1" in result) and (("+CREG: 0,3" in result) or ("+CREG: 0,1" in result)) and ("LTE" in result):
    print("current network is 4G")
    return True
   else:
    print("current network not is 4G")
    return False
  elif "5G" == exceptNetwork:
   if ("+CGREG: 0,1" in result) and ("+CEREG: 0,1" in result) and (("+CREG: 0,0" in result) or ("+CREG: 0,1" in result)) and ("NR5G" in result):
    print("current network is 5G")
    return True
   else:
    print("current network not is 5G")
    return False
 
 # 获取设备内存信息并记录
 def getMemInfo(self,logFile,device_serial=""):
  if device_serial != "":
   debug_serial = "-s {}".format(device_serial)
  self.serial_write(self.at_serial,"adb {} shell cat /proc/meminfo\r\n".format(device_serial))
  result = self.serial_read(self.at_serial)
  with open(logFile, 'a') as file_object:
   file_object.write(result)
 
 # 获取CPU加载信息并记录
 def getCpuLoading(self,logFile,device_serial=""):
  if device_serial != "":
   debug_serial = "-s {}".format(device_serial)
  self.serial_write(self.at_serial,"adb {} shell top -n 1\r\n".format(device_serial))
  result = self.serial_read(self.at_serial)
  with open(logFile, 'a') as file_object:
   file_object.write(result)
 
 # 检查端口是否存在
 def checkPortIsExists(self,portNum):
  port_list = list(serial.tools.list_ports_windows.comports())
  for i in range(len(port_list)):
   if "portNum" in port_list[i].device:
    print("{} is exist".format(portNum))
    return True
  print("{} not exist".format(portNum))
  return False